import { useMemo, useEffect, useState, useRef, useImperativeHandle, forwardRef, useCallback } from 'react';
import * as echarts from 'echarts';
import { Menu, Dropdown, Modal, message, Breadcrumb, Typography } from 'antd';
import { InbizIcon, useEvents, singleTimeOut, getEditor } from '@inbiz/utils';
import FilterModal from '@inbiz/basic/BiFilterModal';
import type { BIProps } from '../data.d';
import { getData as serviceData } from '../service';
import _ from 'lodash';
import { TextWidget, getMessage } from '@inbiz/react';
import { observer } from '@formily/react';
import './style.less';
import api from '../api';
type EChartsOption = echarts.EChartsOption;
const { Text } = Typography;

export default observer(function Content(props: BIProps) {
  const {
    ref,
    values,
    mapLegend = {},
    filter = [],
    detailView,
    detailViewHref,
    dataLabel,
    titlePosition,
    legendPosition,
    borderColor,
    mapBackground,
    borderWidth,
    mapdata,
    colorPattern,
    title,
    style,
    maptitleColor,
    titleFontSize,
    ifShowMapLegend = true,
    legendColor,
    labelColor,
  } = props;
  const [data, setData] = useState<any>({});
  const [filterModalVisiable, setFilterModalVisiable] = useState(false);
  const [dblClickItem, setDblClickItem] = useState('');
  const [filterConditions, setFilterConditions] = useState([]);
  const [downNames, setDownNames] = useState([]);
  const [inited, $inited] = useState(false);
  const [initSuccess, setInitSuccess] = useState(false);
  const [dataIsEmpty, $dataIsEmpty] = useState(false);
  const filterModal = useRef();
  const BIPie: any = useRef();
  const dom: any = useRef()
  const [configEvents] = useEvents(props.callBackEvents, props.emit);
  const getData = useCallback(async (params: object) => {
    const newParams = (await configEvents.current?.onParams?.(params)) || params;
    const data = await (configEvents.current?.onRequest || serviceData)(newParams as any)
    return await configEvents.current?.onData?.(data) || data
  }, []);
  const isEditor = getEditor();
  let __title = title?.status
    ? titlePosition == 'left' || titlePosition == 'right'
      ? getMessage(title.value).split('').join('\n')
      : getMessage(title.value)
    : '';

  let option: EChartsOption = useMemo(() => {
    //标题位置
    let _title: any = {
      left: '',
      top: '',
      right: '',
      bottom: '',
      orient: '',
    };
    switch (titlePosition) {
      case 'left':
        _title.left = '2%';
        _title.top = 'center';
        delete _title.right;
        delete _title.bottom;
        break;
      case 'top':
        _title.left = 'center';
        _title.top = '2%';
        delete _title.right;
        delete _title.bottom;
        break;
      case 'right':
        _title.right = '2%';
        _title.top = 'center';
        delete _title.left;
        delete _title.bottom;
        break;
      case 'bottom':
        _title.left = 'center';
        _title.bottom = '1%';
        delete _title.right;
        delete _title.top;
        break;
    }

    // tooltip
    let _formatter = '';
    if (dataLabel.includes('type')) {
      _formatter += `{b}: `;
    }
    if (dataLabel.includes('value')) {
      _formatter += `{c} `;
    }
    if (dataLabel.includes('ratio')) {
      _formatter += ` {d}%`;
    }

    //图例位置
    let _legend: any = {
      left: '',
      top: '',
      right: '',
      bottom: '',
      orient: '',
    };
    switch (legendPosition) {
      case 'left':
        _legend.left = '8%';
        _legend.top = 'center';
        (_legend.orient = 'vertical'), delete _legend.right;
        delete _legend.bottom;
        break;
      case 'top':
        _legend.left = 'center';
        _legend.top = '9%';
        _legend.orient = 'horizontal';
        delete _legend.right;
        delete _legend.bottom;
        break;
      case 'right':
        _legend.right = '10%';
        _legend.top = 'center';
        _legend.orient = 'vertical';
        delete _legend.left;
        delete _legend.bottom;
        break;
      case 'bottom':
        _legend.left = 'center';
        _legend.bottom = '8%';
        _legend.orient = 'horizontal';
        delete _legend.right;
        delete _legend.top;
        break;
    }

    return ({
      title: {
        text: __title,
        ..._title,
        textStyle: {
          color: maptitleColor || '#000',
          fontSize: titleFontSize || 20,
        },
      },
      color: colorPattern.colorArray,
      tooltip: {
        // formatter: _formatter,
        formatter: `{b}: {c}`,
      },
      legend: {
        type: 'scroll',
        icon: 'circle',
        ..._legend,
        data: data?.xAxis,
        textStyle: {
          color: legendColor || '#999',
        },
        show: ifShowMapLegend !== false,
      },
      series: [
        {
          type: 'pie',
          radius: '50%',
          data: _.map(data?.series?.[0]?.data, (item: any, index: string | number) => {
            return {
              value: item,
              name: data?.xAxis[index],
            };
          }),
          label: {
            show: !_.isEmpty(dataLabel),
            formatter: _formatter,
            alignTo: 'labelLine',
            color: labelColor || '#999',
          },
          emphasis: {
            itemStyle: {
              shadowBlur: 10,
              shadowOffsetX: 0,
              shadowColor: 'rgba(0, 0, 0, 0.5)',
            },
          },
        },
      ],
    });
  }, [data, titlePosition, dataLabel, legendPosition, colorPattern, title, __title, mapBackground]);

  const getPieData = (params: { conditions?: any; downNames?: any }) => {
    if (
      (mapdata?.dataName?.OutId && !_.isEmpty(values) && !_.isEmpty(mapLegend)) ||
      (mapdata?.dataName?.OutId && _.isEmpty(values) && _.isEmpty(mapLegend) && initSuccess)
    ) {
      getData({
        soureOutId: mapdata?.dataName?.OutId,
        dbSearch: {
          XAxis: mapLegend?.[0],
          countColumn: values,
          conditions: params?.conditions || filterConditions,
          downValues: _.map(params?.downNames || downNames, (item) => {
            return {
              legend: '图例',
              xAxis: item,
            };
          }),
        },
      })
        .then((res) => {
          setData(res);
          $inited(true);
          setInitSuccess(true);
          $dataIsEmpty(_.isEmpty(res));
        })
        .catch(() => {
          $inited(true);
          setInitSuccess(true);
        });
    } else {
      $inited(true);
    }
  };

  const handleItemClick = (key: string, item: string) => {
    if (!item && key == 'down') {
      // 未选中图表内容
      message.warning(getMessage('BIPieChart.lang.chartContentNotSelected'));
      return;
    }
    setDblClickItem('');
    switch (key) {
      case 'detail':
        handleMapClick();
        break;
      case 'down':
        setDownNames((state) => {
          if (state.length >= 5) {
            // 最多下探5级
            message.warning(getMessage('BIPieChart.lang.fiveLevel'));
            return state;
          }
          return [...state, item];
        });
        break;
      default:
        break;
    }
  };

  const menu = useMemo(() => {
    return (
      <Menu
        onClick={(e) => {
          handleItemClick(e?.key, dblClickItem);
        }}
        items={[
          {
            key: 'detail',
            // 跳转详情
            label: (
              <span>
                <TextWidget>BIPieChart.lang.goToDetail</TextWidget>
              </span>
            ),
            disabled: !detailViewHref || detailView == 'none',
          },
          {
            key: 'down',
            // 下探
            label: (
              <span>
                <TextWidget>BIPieChart.lang.down</TextWidget>
              </span>
            ),
            disabled: downNames?.length >= mapLegend?.[0]?.DownColumns?.length,
          },
        ]}
      />
    );
  }, [dblClickItem]);

  const handleMapClick = (params) => {
    props.emit?.('onClick', params);
    if (detailView == 'skip' && detailViewHref) {
      window.open(detailViewHref);
    }
  };

  const onOk = async () => {
    if (filterModal.current && filterModal.current?.submit) {
      const newFilter = await filterModal.current?.submit();
      setFilterConditions(newFilter);
      setFilterModalVisiable(false);
    }
  };

  useEffect(() => {
    if (dom.current) {
      // 1.BIPie.current作为优化条件影响到数据为空时的渲染
      // 2.增加dataIsEmpty字段知晓上一轮的数据是否空
      // 2023/4/20 条件有问题，影响了数据渲染，注掉了
      // if (!BIPie.current || dataIsEmpty) {
      // }
      let myChart = echarts.init(dom.current);
      BIPie.current = myChart;

      //单击
      myChart.on('click', function (params: any) {
        handleMapClick(params);
      });

      //双击
      myChart.on('dblclick', function (params: any) {
        setDownNames((state) => {
          if (state?.length >= 5) {
            message.warning(getMessage('BIPieChart.lang.fiveLevel'));
            return state;
          }
          if (state?.length >= mapLegend?.[0]?.DownColumns?.length) {
            return state;
          }
          return [...state, params?.name];
        });
      });

      //右键
      myChart.on('contextmenu', function (params: any) {
        setDblClickItem(params?.name);
      });
    }
  }, [data]);

  const _setOption = async () => {
    BIPie?.current.clear();
    const _option = (await configEvents.current?.onEchartsOptions?.(option)) || option;
    if (isEditor) {
      let chartDom = document.getElementById(props?.controlId);
      BIPie.current.resize({ width: chartDom?.clientWidth, height: chartDom?.clientHeight });
      _option && BIPie?.current.setOption(_option, { lazyUpdate: true });
    } else {
      singleTimeOut(() => {
        let chartDom = document.getElementById(props?.controlId);
        BIPie.current.resize({ width: chartDom?.clientWidth, height: chartDom?.clientHeight });
        _option && BIPie?.current.setOption(_option, { lazyUpdate: true });
      }, 600, props?.controlId)
    };
  };

  // setOption
  useEffect(() => {
    if (BIPie?.current) {
      _setOption();
    }
  }, [option, data, BIPie.current, dom.current]);

  useEffect(() => {
    getPieData({ downNames, conditions: filterConditions });
  }, [downNames, props, filterConditions]);

  //自适应宽高
  useEffect(() => {
    let chartDom = dom.current;
    if (BIPie.current && chartDom) {
      BIPie.current.resize({ width: chartDom?.clientWidth, height: chartDom?.clientHeight });
    };
  }, [props]);

  useImperativeHandle(
    ref,
    () => api(configEvents, {
      data, setData, BIPie
    }),
    [data],
  );

  return (
    <div
      className="inbiz-BIPieChart-content-warpper"
      style={
        borderWidth
          ? {
            ...mapBackground.style,
            border: `${borderWidth}px solid ${borderColor}`,
            backgroundPosition: 'center',
            // backgroundRepeat: 'no-repeat',
            backgroundSize: '100%, 100%',
          }
          : {
            ...mapBackground.style,
            backgroundPosition: 'center',
            // backgroundRepeat: 'no-repeat',
            backgroundSize: '100%, 100%',
          }
      }
    >
      {_.isEmpty(data) ? (
        inited && (
          <div className="emptyDataContainer">
            <InbizIcon style={{ fontSize: 120 }} type="icon-inbiz-BI-queshengtu" />
            {/* 请添加数据 */}
            <div style={{ color: '#c2c2c2' }}>
              <TextWidget>BIPieChart.lang.needData</TextWidget>
            </div>
          </div>
        )
      ) : (
        <Dropdown overlay={menu} trigger={['contextMenu']}>
          <div ref={dom} className="inbiz-BIPieChart-dom" />
        </Dropdown>
      )}
      {filter.length > 0 && mapLegend?.[0] && values ? (
        <div
          style={{
            position: 'absolute',
            top: '16px',
            right: '16px',
            width: 24,
            height: 24,
            border: '1px solid #aaa',
            borderRadius: 3,
            display: 'flex',
            justifyContent: 'center',
            alignItems: 'center',
            cursor: 'pointer',
          }}
          className="inbiz-BIPieChart-filter-icon-warpper"
          onClick={() => {
            setFilterModalVisiable(true);
          }}
        >
          <InbizIcon type="icon-a-shaixuantubiao" className="inbiz-BIPieChart-filter-icon" />
        </div>
      ) : null}
      {!_.isEmpty(downNames) && (
        <>
          <div
            style={{
              position: 'absolute',
              top: '0',
              left: '0',
            }}
          >
            <div
              style={{ color: '#1890ff', cursor: 'pointer' }}
              onClick={() => {
                setDownNames((state) => {
                  return state.slice(0, state.length - 1);
                });
              }}
            >
              {/* 返回 */}
              <InbizIcon
                type="icon-inbiz_other-return"
                // onClick={() => handleReturn(mydownValues.current.length - 1)}
                style={{ position: 'absolute', color: maptitleColor || '#000', top: 3 }}
              />
            </div>
            <div>
              <Breadcrumb className="inbiz-pie-breadcrumb" separator={<span style={{ color: maptitleColor || '#000' }}>/</span>}>
                {_.map(downNames, (item) => {
                  return (
                    <Breadcrumb.Item
                      key={item}
                      onClick={() => {
                        setDownNames((state) => {
                          if (state.length == 1) {
                            return state;
                          }
                          let _state = state;
                          let _index = _.indexOf(_state, item);
                          _state = _state.slice(0, _index + 1);
                          return _state;
                        });
                      }}

                    >

                      <Text style={{
                        cursor: 'pointer', color: maptitleColor || '#000'
                      }}>
                        {item}
                      </Text>
                    </Breadcrumb.Item>
                  );
                })}
              </Breadcrumb>
            </div>
          </div>
        </>
      )}
      <Modal
        // 筛选条件
        title={getMessage('BIPieChart.lang.filterOption')}
        visible={filterModalVisiable}
        onCancel={() => {
          setFilterModalVisiable(false);
        }}
        onOk={onOk}
        getContainer={false}
        destroyOnClose
        cancelText={getMessage('global.cancel')}
        okText={getMessage('global.sure')}
      >
        <FilterModal
          list={_.isEmpty(filterConditions) ? filter : filterConditions}
          active={0}
          refs={filterModal}
        />
      </Modal>
    </div>
  );
});
